home *** CD-ROM | disk | FTP | other *** search
/ Die Ultimative Software-P…i Collection 1996 & 1997 / Die Ultimative Software-Pakete CD-ROM fur Atari Collection 1996 & 1997.iso / g / gnu_c / gempp19.zoo / gem++19 / src / flyform.cc < prev    next >
Encoding:
C/C++ Source or Header  |  1993-11-01  |  6.2 KB  |  232 lines

  1. /*
  2. AUTHOR:
  3. ------------------------------------------------------------------------------
  4. Markus Gutschke | Internet: srb242@math.uni-muenster.de
  5. Papenbusch 31   |           Markus.Gutschke@uni-muenster.de
  6. 48159 M"unster  |-------------------------------------------------------------
  7. W-Germany       | "Death --- no excuse for not working!" 
  8.                 |                          ('Supreme Being' in 'Time Bandits')
  9. */
  10.  
  11. #include <aesbind.h>
  12. #include <gemfast.h>
  13. #include <macros.h>
  14. #include <stdlib.h>
  15. #include <stdarg.h>
  16. #include <string.h>
  17. #include <vdibind.h>
  18.  
  19. /* header for rectangle buffers (invisible to global functions)     */
  20.  
  21. typedef struct {
  22.     long    magic;
  23.     int     vdihandle;
  24.     int     pxy[8];
  25.     MFDB    mfdb,scr;
  26.     char    data[1];
  27. } Buffer;
  28.  
  29. /* check, if two rectangles intersect                               */
  30.  
  31. static int  intersect(int  x1,int  y1,int  w1,int  h1,
  32.                       int  x2,int  y2,int  w2,int  h2,
  33.                       int *x3,int *y3,int *w3,int *h3)
  34. {
  35.     *x3 = max(x1,x2);
  36.     *y3 = max(y1,y2);
  37.     *w3 = min(x1+w1-1,x2+w2-1) - *x3 + 1;
  38.     *h3 = min(y1+h1-1,y2+h2-1) - *y3 + 1;
  39.     return ((*w3 > 0) && (*h3 > 0));
  40. }
  41.  
  42. /* save screen rectangle and return handle                          */
  43.  
  44. void    *flysave(int vdihandle,int x,int y,int w,int h)
  45. {
  46.     int     workout[57];
  47.     Buffer  *buffer;
  48.     long    size;
  49.     int     planes,wdwidth;
  50.  
  51.     vq_extnd(vdihandle,1,workout);
  52.     planes = workout[4];
  53.     wdwidth = (int)((w + 15) / 16);
  54.     size = sizeof(Buffer) + long(planes)*h*2*wdwidth;
  55.     if ((buffer = (Buffer*)malloc(size)) == 0)
  56.         return(0);
  57.     else {
  58.         buffer->magic = 0x4711;
  59.         buffer->vdihandle       = vdihandle;
  60.         buffer->mfdb.fd_addr    = (long)&buffer->data;
  61.         buffer->mfdb.fd_w       = w;
  62.         buffer->mfdb.fd_h       = h;
  63.         buffer->mfdb.fd_wdwidth = wdwidth;
  64.         buffer->mfdb.fd_stand   = 0;
  65.         buffer->mfdb.fd_nplanes = planes;
  66.         buffer->scr.fd_addr     =
  67.         buffer->scr.fd_w        = 
  68.         buffer->scr.fd_h        = 
  69.         buffer->scr.fd_wdwidth  = 
  70.         buffer->scr.fd_stand    =
  71.         buffer->scr.fd_nplanes  = 0;
  72.         buffer->pxy[0]          = x;
  73.         buffer->pxy[1]          = y;
  74.         buffer->pxy[2]          = x + w - 1;
  75.         buffer->pxy[3]          = y + h - 1;
  76.         buffer->pxy[4]          = 0;
  77.         buffer->pxy[5]          = 0;
  78.         buffer->pxy[6]          = w-1;
  79.         buffer->pxy[7]          = h-1;
  80.         graf_mouse(M_OFF,0);
  81.         vro_cpyfm(vdihandle,S_ONLY,buffer->pxy,
  82.                   &buffer->scr,&buffer->mfdb);
  83.         graf_mouse(M_ON,0);
  84.         return(buffer); }
  85. }
  86.  
  87. /* restore saved screen rectangle                                   */
  88.  
  89. void    flyrestore(void *buffer)
  90. {
  91.     #define buffer  ((Buffer *)buffer)
  92.     int     pxy[8];
  93.     int     *s,*d;
  94.  
  95.     if (buffer != 0 && buffer->magic == 0x4711) {
  96.         buffer->magic = 0;
  97.         d = pxy; s = buffer->pxy+4;
  98.         *d++ = *s++; *d++ = *s++; *d++ = *s++; *d++ = *s++;
  99.         d = pxy+4; s = buffer->pxy;
  100.         *d++ = *s++; *d++ = *s++; *d++ = *s++; *d++ = *s++;
  101.         graf_mouse(M_OFF,0);
  102.         vro_cpyfm(buffer->vdihandle,S_ONLY,pxy,
  103.                   &buffer->mfdb,&buffer->scr);
  104.         graf_mouse(M_ON,0);
  105.         free(buffer); }
  106.     return;
  107.     
  108.     #undef  buffer
  109. }
  110.  
  111. /* move previously stored rectangle to new position                 */
  112.  
  113. static void     *scrmove(void *buffer,int nx,int ny)
  114. {
  115.     #define buffer  ((Buffer *)buffer)
  116.     Buffer  *newbuffer;
  117.     int     w,h;
  118.     int     rx,ry,rw,rh;
  119.     int     pxy[8],rst[8];
  120.  
  121.     if (buffer != 0 && buffer->magic == 0x4711) {
  122.         graf_mouse(M_OFF,0);
  123.         w = buffer->pxy[2]-buffer->pxy[0]+1;
  124.         h = buffer->pxy[3]-buffer->pxy[1]+1;
  125.         newbuffer = (Buffer*) flysave(buffer->vdihandle,nx,ny,w,h);
  126.         if (newbuffer == 0) {
  127.             form_dial(FMD_FINISH,0,0,0,0,nx,ny,w,h);
  128.             flyrestore(buffer);
  129.             return(0); }
  130.         buffer->magic = 0;
  131.         pxy[0] = buffer->pxy[0];
  132.         pxy[1] = buffer->pxy[1];
  133.         pxy[2] = buffer->pxy[2];
  134.         pxy[3] = buffer->pxy[3];
  135.         pxy[6] = (pxy[4] = nx) + w - 1;
  136.         pxy[7] = (pxy[5] = ny) + h - 1;
  137.         if (intersect(pxy[0],pxy[1],w,h,
  138.                       pxy[4],pxy[5],w,h,
  139.                       &rx,&ry,&rw,&rh)) {
  140.             rst[2] = (rst[0] = rx - pxy[0]) + rw - 1;
  141.             rst[3] = (rst[1] = ry - pxy[1]) + rh - 1;
  142.             rst[6] = (rst[4] = rx - nx) + rw - 1;
  143.             rst[7] = (rst[5] = ry - ny) + rh - 1;
  144.             vro_cpyfm(buffer->vdihandle,S_ONLY,rst,
  145.                       &buffer->mfdb,&newbuffer->mfdb); }
  146.         vro_cpyfm(buffer->vdihandle,S_ONLY,pxy,&buffer->scr,&buffer->scr);
  147.         if (intersect(pxy[0],pxy[1],w,h,
  148.                       pxy[0],pxy[1],pxy[6]-pxy[0]+1,pxy[5]-pxy[1],
  149.                       &rx,&ry,&rw,&rh)) {
  150.             rst[2] = (rst[0] = rx - pxy[0]) + rw - 1;
  151.             rst[3] = (rst[1] = ry - pxy[1]) + rh - 1;
  152.             rst[6] = (rst[4] = rx) + rw - 1;
  153.             rst[7] = (rst[5] = ry) + rh - 1;
  154.             vro_cpyfm(buffer->vdihandle,S_ONLY,rst,&buffer->mfdb,&buffer->scr);}
  155.         if (intersect(pxy[0],pxy[1],w,h,
  156.                       pxy[6]+1,pxy[1],pxy[2]-pxy[6],pxy[7]-pxy[1]+1,
  157.                       &rx,&ry,&rw,&rh)) {
  158.             rst[2] = (rst[0] = rx - pxy[0]) + rw - 1;
  159.             rst[3] = (rst[1] = ry - pxy[1]) + rh - 1;
  160.             rst[6] = (rst[4] = rx) + rw - 1;
  161.             rst[7] = (rst[5] = ry) + rh - 1;
  162.             vro_cpyfm(buffer->vdihandle,S_ONLY,rst,&buffer->mfdb,&buffer->scr);}
  163.         if (intersect(pxy[0],pxy[1],w,h,
  164.                       pxy[4],pxy[7]+1,pxy[2]-pxy[4]+1,pxy[3]-pxy[7],
  165.                       &rx,&ry,&rw,&rh)) {
  166.             rst[2] = (rst[0] = rx - pxy[0]) + rw - 1;
  167.             rst[3] = (rst[1] = ry - pxy[1]) + rh - 1;
  168.             rst[6] = (rst[4] = rx) + rw - 1;
  169.             rst[7] = (rst[5] = ry) + rh - 1;
  170.             vro_cpyfm(buffer->vdihandle,S_ONLY,rst,&buffer->mfdb,&buffer->scr);}
  171.         if (intersect(pxy[0],pxy[1],w,h,
  172.                       pxy[0],pxy[5],pxy[4]-pxy[0],pxy[3]-pxy[5]+1,
  173.                       &rx,&ry,&rw,&rh)) {
  174.             rst[2] = (rst[0] = rx - pxy[0]) + rw - 1;
  175.             rst[3] = (rst[1] = ry - pxy[1]) + rh - 1;
  176.             rst[6] = (rst[4] = rx) + rw - 1;
  177.             rst[7] = (rst[5] = ry) + rh - 1;
  178.             vro_cpyfm(buffer->vdihandle,S_ONLY,rst,&buffer->mfdb,&buffer->scr);}
  179.         graf_mouse(M_ON,0);
  180.         free(buffer);
  181.         return(newbuffer); }
  182.     return(0);
  183.     
  184.     #undef  buffer
  185. }
  186.  
  187. void flyfly(int vdihandle, void **buffer, int* dx, int* dy, int opaque)
  188. {
  189.     #define buffer  ((Buffer **)buffer)
  190.  
  191.     int     x,y,w,h;
  192.     int     orgx,orgy;
  193.     int     wx,wy,ww,wh;
  194.     int     posx,posy,mx,my,mb,mk;
  195.  
  196.     orgx=x=(*buffer)->pxy[0];
  197.     orgy=y=(*buffer)->pxy[1];
  198.     w=(*buffer)->mfdb.fd_w;
  199.     h=(*buffer)->mfdb.fd_h;
  200.  
  201.     wind_get(0,WF_WORKXYWH,&wx,&wy,&ww,&wh);
  202.  
  203.     if (!opaque) {
  204.         flyrestore(*buffer);
  205.         graf_dragbox(w,h,x,y,wx,wy,ww,wh,&x,&y);
  206.         *dx = x - orgx;
  207.         *dy = y - orgy;
  208.         *buffer = (Buffer*)flysave(vdihandle,x,y,w,h);
  209.     } else {
  210.         graf_mkstate(&mx,&my,&mb,&mk);
  211.  
  212.         posx = x - mx;
  213.         posy = y - my;
  214.  
  215.         while (mb) {
  216.             evnt_mouse(1,mx,my,1,1,&mx,&my,&mb,&mk);
  217.             x = mx + posx;
  218.             y = my + posy;
  219.             if (x + w > wx + ww) x = wx + ww - w;
  220.             if (x < wx) x = wx;
  221.             if (y + h > wy + wh) y = wy + wh - h;
  222.             if (y < wy) y = wy;
  223.             *buffer = (Buffer*) scrmove(*buffer,x,y);
  224.         }
  225.  
  226.         *dx = x - orgx;
  227.         *dy = y - orgy;
  228.     }
  229.  
  230.     #undef buffer
  231. }
  232.